home *** CD-ROM | disk | FTP | other *** search
/ Apple II Magazines (PO) / Nibble Volume 09, No. 11 (1988-11)(MicroSPARC)(Side A).zip / Nibble Volume 09, No. 11 (1988-11)(MicroSPARC)(Side A).po / SPEEDDRAW.0.S < prev    next >
Text File  |  1996-12-24  |  14KB  |  470 lines

  1. *
  2. * SPEEDDRAW Source Code
  3. * by Jim Savage
  4. * Copyright(c) 1988
  5. * MicroSPARC, Inc.
  6. * Concord, MA 01742
  7. *
  8. * Merlin assembler
  9. *
  10. * Equates for installation
  11. *
  12. DISTANCE  EQU $00
  13. LENGTH    EQU $2F        ;Length of command minus one
  14. PCL       EQU $3A        ;Pointer for disassembly
  15. A1L       EQU $3C
  16. A2L       EQU $3E
  17. A4L       EQU $42
  18. STREND    EQU $6F
  19. HIMEM     EQU $73
  20. AMPER     EQU $3F5
  21. INSDS2    EQU $F88C      ;Monitor disassembly routine
  22. MOVE      EQU $FE2C
  23. GETBUF    EQU $BEF5
  24. *
  25.           ORG $4069
  26. *
  27.           LDY #$0A
  28.           LDA AMPER+1
  29.           STA PCL
  30.           LDA AMPER+2
  31.           STA PCL+1
  32. ]LOOP     LDA (PCL),Y    ;Look at memory where ampersand points
  33.           CMP INTERP,Y   ;See if it's Ampertrig
  34.           BNE INSTALL    ;Not same so install
  35.           DEY            ;Check another byte
  36.           BNE ]LOOP      ;Until 10 are OK
  37.           RTS            ;Don't want to repeat installation
  38. *
  39. INSTALL   LDA AMPER+1    ;Get old vector
  40.           STA OLDVEC+1   ;  and link
  41.           LDA AMPER+2    ;    so it can
  42.           STA OLDVEC+2   ;      still be used
  43.           LDA #$4C       ;JMP instruction
  44.           STA AMPER
  45. *
  46.           LDA $BF00      ;Check for Prodos
  47.           CMP #$4C
  48.           BEQ PRO        ;Yes, use GETBUF
  49. *
  50.           LDA HIMEM+1    ;Get old HIMEM location
  51.           SEC
  52.           SBC #$04       ;Need 4 pages of memory
  53.           STA HIMEM+1    ;Move it down
  54.           STA STREND+1   ;Also the string start
  55.           BNE SETPTRS    ;Always
  56. *
  57. PRO       LDA #04
  58.           JSR GETBUF     ;Ask for 4 page buffer
  59. *
  60. SETPTRS   STA A4L+1      ;Point MOVE to new home
  61.           STA AMPER+2    ;And point ampersand vector at it
  62.           STA GOTCMD+1   ;Take care of high byte
  63.           SEC
  64.           SBC #>INTERP   ;Find how far to move
  65.           STA DISTANCE
  66. *
  67.           LDA #>INTERP   ;Start of resident part
  68.           STA PCL+1      ;Put in relocation pointer
  69.           STA A1L+1      ;  and in MOVE origin
  70.           LDY #00        ;Put
  71.           STY PCL        ;  zero
  72.           STY AMPER+1    ;    in
  73.           STY A1L        ;      various
  74.           STY A4L        ;        places
  75.           STY STREND     ;
  76.           STY HIMEM      ;
  77. *
  78. RELOC8    LDX #00
  79.           JSR INSDS2     ;Disassemble an instruction
  80.           LDY LENGTH     ;How long?
  81.           CPY #02        ;A 3-byter?
  82.           BNE NXTINST
  83.           LDA (PCL),Y    ;Get the 3rd byte
  84.           CMP #>INSTALL  ;Below our code?
  85.           BMI NXTINST    ;Yes, don't adjust
  86.           CMP #>END+$100 ;Above our code?
  87.           BPL NXTINST    ;Yes, don't adjust
  88.           CLC
  89.           ADC DISTANCE   ;Adjust the address
  90.           STA (PCL),Y    ;Put it back
  91. NXTINST   INY
  92.           TYA
  93.           CLC
  94.           ADC PCL        ;Advance the pointer
  95.           STA PCL
  96.           BCC NOPAGE
  97.           INC PCL+1
  98. NOPAGE    LDY #00
  99.           LDA (PCL),Y    ;Look at next byte
  100.           BNE RELOC8     ;If not zero, keep on
  101. *
  102.           LDA #<END-1
  103.           STA A2L        ;Finish preparing for MOVE
  104.           LDA #>END-1
  105.           STA A2L+1
  106.           JMP MOVE       ;Exit via the move
  107. *
  108. *  Equates for resident routine
  109. *
  110. ANG1      EQU $00
  111. QUAD1     EQU $01
  112. ANG2      EQU $02
  113. QUAD2     EQU $03
  114. XCH       EQU $04
  115. XCL       EQU $05
  116. YCH       EQU $06
  117. YCL       EQU $07
  118. RAD       EQU $08
  119. VARTAB    EQU $69
  120. TXTPTR    EQU $B8
  121. SINE      EQU $2F0
  122. SINRAD    EQU $2F1
  123. LOCENT    EQU $2F2
  124. HICENT    EQU $2F3
  125. SPEED     EQU $2F4
  126. COUNT     EQU $2F6
  127. HPLOT0    EQU $F457
  128. *
  129. *
  130. INTERP    LDY #00
  131.           LDX #09        ;End of command table
  132.           LDA (TXTPTR),Y ;Get command character
  133.           CMP #'&'       ;Second ampersand?
  134.           BEQ TRYOLD     ;Yes, so not an Ampertrig command
  135. CMDLOOP   CMP CMDTBL,X   ;Look for match
  136.           BEQ GOTCMD     ;Found
  137.           DEX
  138.           BPL CMDLOOP    ;No, next
  139.           BMI OLDVEC
  140. TRYOLD    INC TXTPTR     ;Step beyond ampersand
  141.           BNE OLDVEC
  142.           INC TXTPTR+1
  143. OLDVEC    JMP $0000      ;Send to address formerly in AMPER
  144. GOTCMD    LDA #$00       ;Loader puts hi byte of cmds here
  145.           PHA
  146.           LDA CALLTBL,X  ;Set up the address
  147.           PHA            ;  for the "funny jump"
  148. *
  149. ]LOOP     INC TXTPTR     ;Advance
  150.           BNE NOCARI2
  151.           INC TXTPTR+1
  152. NOCARI2   LDA (TXTPTR),Y ;  until
  153.           BEQ INPUTS     ;    zero
  154.           CMP #$3A       ;      or colon
  155.           BNE ]LOOP      ;Keep looking
  156. *
  157. INPUTS    LDX #00        ;Index to input targets
  158.           LDY #$02       ;Index to variable table
  159.           JSR TWOBYTE    ;Move A1%
  160.           JSR TWOBYTE    ;Move A2%
  161.           JSR TWOBYTE    ;Move XC%
  162.           JSR TWOBYTE    ;Move YC%
  163.           INY            ;Just a low byte
  164.           JSR MOVBYTE    ;Move R%
  165.           LDX #00        ;Index to ANG1
  166.           JSR DIV90      ;Convert degrees to Hex
  167.           LDX #02        ;Index to ANG2
  168.           JMP DIV90      ;Again, then funny jump to command
  169. *
  170. RAY       JSR DODOT
  171.           LDA RAD        ;Check if done
  172.           BEQ DONEVEC    ;Yes
  173.           DEC RAD        ;Next one
  174.           JMP RAY
  175. *
  176. DOTLIN    LDA #03        ;Start in mid-dash
  177.           STA COUNT
  178. ]LOOP     JSR BDOT       ;Draw a dot or not
  179.           LDA RAD        ;Check if done
  180.           BEQ DONEVEC    ;Yes
  181.           DEC RAD
  182.           JMP ]LOOP      ;Next
  183. *
  184. VECTOR    LDA RAD
  185.           PHA            ;Put radius aside
  186.           JSR RAY        ;Draw the line
  187.           PLA            ;Retrieve radius
  188.           STA RAD
  189. MOVEC     JSR GETX
  190.           LDY #$11       ;Index to XC% low
  191.           STA (VARTAB),Y ;Put away
  192.           STA XCL
  193.           LDA HICENT
  194.           DEY            ;XC% high
  195.           STA (VARTAB),Y ;  away
  196.           STA XCH
  197.           JSR GETY
  198.           LDY #$18       ;Index to YC% low
  199.           STA (VARTAB),Y ;  away
  200.           STA YCL
  201.           LDA HICENT
  202.           DEY
  203.           STA (VARTAB),Y ;YC% high
  204.           STA YCH
  205. DONEVEC   RTS
  206. *
  207. BARC      LDA #03        ;Start in mid-dash
  208.           STA COUNT
  209.           JSR SETSPD     ;Set speed appropriate to radius
  210. ]LOOP     JSR BDOT
  211.           JSR NXTANGL
  212.           BNE ]LOOP      ;Another dot or not
  213.           JMP BDOT       ;Last one
  214. *
  215. CIRCLE    LDA #00        ;Zero the
  216.           STA ANG1       ;  start
  217.           STA ANG2       ;    and
  218.           STA QUAD1      ;      finish
  219.           STA QUAD2      ;        angles
  220. *
  221. ARC       JSR SETSPD     ;Set speed appropriate to radius
  222. ]LOOP     JSR DODOT
  223.           JSR NXTANGL
  224.           BNE ]LOOP      ;Another dot, else do last one
  225. *
  226. DODOT     JSR GETY
  227.           SEC
  228.           CMP #192       ;Legal Y?
  229.           BCS RTS1       ;Too big, punt
  230.           LDY HICENT     ;Hi byte <> 0?
  231.           BNE RTS1       ;Return without plotting
  232.           PHA            ;Put Y aside
  233.           JSR GETX
  234.           TAX            ;Put XL where HPLOT0 wants it
  235.           PLA            ;Retrieve Y-coordinate
  236.           LDY HICENT     ;Put XH where HPLOT0 wants it
  237.           BMI RTS1       ;Can't have negative X coord
  238.           CPY #01        ;Check for oversize X coord
  239.           BMI PLOTIT     ;O.K.
  240.           BEQ CHEKLO     ;Look at lo byte
  241. RTS1      RTS            ;Hi byte 2 or more, too big.
  242. CHEKLO    SEC
  243.           CPX #$18       ;X bigger than 279?
  244.           BCS RTS1       ;Yes, return without plotting
  245. PLOTIT    JMP HPLOT0     ;Dot done!
  246. *
  247. LTURN1    JMP LTURN      ;Just so all commands are on 1 page
  248. *
  249. TURN      INC QUAD1      ;Right turn
  250.           JSR MOVEC      ;Set center
  251.           DEC QUAD1      ;Face
  252.           DEC QUAD1      ;  outward
  253.           CLC
  254.           LDY #$0A
  255.           LDA (VARTAB),Y ;Get A2% lo
  256.           LDY #03
  257.           ADC (VARTAB),Y ;Add A1% lo
  258.           STA (VARTAB),Y ;Update A1% lo
  259.           STA QUAD2      ;Set finish angle
  260.           LDY #09
  261.           LDA (VARTAB),Y ;Likewise the hi bytes
  262.           LDY #02
  263.           ADC (VARTAB),Y
  264.           STA (VARTAB),Y ;Put in A1%
  265.           STA ANG2
  266.           LDX #02
  267.           JSR DIV90      ;Convert to hex degrees
  268.           DEC QUAD2      ;Face outward
  269.           JSR ARC
  270.           JMP MOVEC      ;Set origin at end & exit
  271. *
  272. LTURN     SEC
  273.           LDY #03
  274.           LDA (VARTAB),Y ;Get A1% low
  275.           LDY #$0A
  276.           SBC (VARTAB),Y ;Subtract A2% low
  277.           LDY #03
  278.           STA (VARTAB),Y ;New angle in A1% low
  279.           DEY
  280.           LDA (VARTAB),Y ;Likewise hi byte
  281.           LDY #09
  282.           SBC (VARTAB),Y
  283.           LDY #02
  284.           STA (VARTAB),Y
  285.           LDA ANG1       ;Move 1
  286.           STA ANG2       ;  to 2
  287.           LDA QUAD1
  288.           STA QUAD2
  289.           DEC QUAD1      ;Face in
  290.           JSR MOVEC      ;Set center
  291.           JSR GETA1      ;Get the (new) input A1%
  292.           INC QUAD2      ;Face out
  293.           JSR ARC        ;Do turn
  294.           JSR GETA1      ;Restore (new) input A1%
  295.           JMP MOVEC      ;Put center at end: Done
  296. *
  297. GETA1     LDX #00
  298.           LDY #02
  299.           JSR TWOBYTE    ;Move input A1% to ANG1/QUAD1
  300.           LDX #00
  301.           JSR DIV90
  302.           INC QUAD1
  303.           RTS
  304. *
  305. SETSPD    LDA QUAD2
  306.           AND #03        ;Always work in 1st 4 quadrants
  307.           STA QUAD2
  308.           LDA #$20       ;Speed=32 if RAD<=5
  309.           STA SPEED
  310.           LDA #05        ;Test criterion
  311. RADTEST   SEC
  312.           CMP RAD
  313.           BCS SET        ;Speed found
  314.           ASL A          ;Double criterion
  315.           LSR SPEED      ;Halve speed
  316.           BNE RADTEST
  317.           INC SPEED      ;Must be at least one
  318. SET       SEC
  319.           LDA #00
  320.           SBC SPEED      ;Make mask for rounding angles
  321.           PHA            ;Put clone aside
  322.           AND ANG1
  323.           STA ANG1
  324.           PLA            ;Retrieve clone
  325.           AND ANG2
  326.           STA ANG2
  327.           RTS
  328. *
  329. NXTANGL   CLC
  330.           LDA SPEED
  331.           ADC ANG1       ;Increment angle by 1,2,4 etc
  332.           STA ANG1
  333.           BCC CHECK
  334.           INC QUAD1      ;If last quad done
  335. CHECK     LDA QUAD1
  336.           AND #03        ;Stay in 4 quadrants
  337.           CMP QUAD2      ;In final quad?
  338.           BNE RTSA       ;No, keep on
  339.           LDA ANG1
  340.           CMP ANG2       ;Same?
  341. RTSA      RTS            ;Return w/ Z-flag set if done
  342. *
  343. BDOT      LDA COUNT      ;Where are we?
  344.           BNE NOTZED     ;Still counting
  345.           LDA #04        ;Reset
  346.           STA COUNT
  347.           RTS
  348. NOTZED    CMP #02        ;In plot part of cycle?
  349.           BMI SKPDOT     ;No, skip
  350.           JSR DODOT      ;Make your point
  351. SKPDOT    DEC COUNT
  352.           RTS
  353. *
  354. GETY      LDA YCL        ;Prepare to calc Y-coordinate
  355.           STA LOCENT
  356.           LDA YCH        ;Allow for center off screen
  357.           STA HICENT
  358.           DEC QUAD1      ;Get ready for cosine
  359.           JSR GETCOORD   ;Go get Y-coordinate
  360.           INC QUAD1      ;Now for sine
  361.           RTS
  362. *
  363. GETX      LDA XCH        ;Get ready for X
  364.           STA HICENT
  365.           LDA XCL
  366.           STA LOCENT
  367.           JSR GETCOORD   ;Go get x-coordinate
  368.           RTS
  369. *
  370. * Generate sine * radius
  371. *
  372. GETCOORD  LDA QUAD1
  373.           AND #$01       ;Odd or even?
  374.           BEQ EVEN
  375.           LDA ANG1
  376.           BEQ SINONE     ;Special case, sine=1
  377.           LDA #$00
  378.           SEC
  379.           SBC ANG1       ;Get complement of angle
  380.           CLC
  381.           BCC EVEN+2
  382. EVEN      LDA ANG1       ;Don't complement
  383.           SEC
  384.           CMP #$F6       ;Big enough that sine=1?
  385.           BCC LOOKUP     ;No, look up sine
  386. SINONE    LDA RAD        ;Yes, so the leg = the radius
  387.           STA SINRAD
  388.           JMP PLUSMNS
  389. LOOKUP    TAY            ;Angle indexes the table
  390.           LDA SINTBL,Y   ;Got the sine!
  391.           STA SINE
  392. *
  393. * Multiply radius by (co)sine  *
  394. *
  395.           LDA #$00
  396.           STA SINRAD
  397.           LDX #$08       ;Set bit index
  398. ]LOOP     ASL A          ;Shift
  399.           ROL SINRAD     ;  three
  400.           ASL SINE       ;    bytes
  401.           BCC NOCARI     ;No carry, no add
  402.           CLC
  403.           ADC RAD
  404.           BCC NOCARI
  405.           INC SINRAD
  406. NOCARI    DEX            ;Next bit
  407.           BNE ]LOOP
  408.           ASL A          ;Round off to closest hi bit
  409.           BCC PLUSMNS
  410.           INC SINRAD
  411. PLUSMNS   LDA QUAD1
  412.           AND #02        ;In neg half of sine wave?
  413.           BNE SUBTRACT   ;Yes
  414.           LDA LOCENT     ;Get lo byte of center
  415.           CLC
  416.           ADC SINRAD     ;Add (sine * radius)
  417.           BCC GOTIT
  418.           INC HICENT
  419. GOTIT     RTS
  420. SUBTRACT  LDA LOCENT     ;Get lo byte of center
  421.           SEC
  422.           SBC SINRAD     ;Subtract (sine * radius)
  423.           BCS GOTIT
  424.           DEC HICENT
  425.           RTS
  426. *
  427. TWOBYTE   JSR MOVBYTE    ;Move high byte
  428.           JSR MOVBYTE    ;Move low byte
  429.           INY            ;5 bumps
  430.           INY            ; to get to
  431.           INY            ; the next
  432.           INY            ; variable
  433.           INY            ; in the table
  434.           RTS
  435. *
  436. MOVBYTE   LDA (VARTAB),Y ;Get byte from variable table
  437.           STA $00,X      ;Put on zero page
  438.           INY            ;Bump
  439.           INX            ;  indices
  440.           RTS
  441. *
  442. DIV90     LDA 00,X       ;Look at hi byte (bytes rev!)
  443.           BPL DODIV      ;If positive, proceed
  444.           CLC
  445.           ADC #$5A       ;Add 360x64 to it
  446.           STA 00,X
  447. DODIV     LDY #00        ;Begin division
  448.           STY $00,X
  449.           LDY #$10       ;Bit index
  450. ]LOOP     ASL $00,X
  451.           ROL $01,X
  452.           ROL A
  453.           CMP #$5A       ;Bigger than 90?
  454.           BCC TOOBIG     ;No
  455.           SBC #$5A
  456.           INC $00,X
  457. TOOBIG    DEY
  458.           BNE ]LOOP
  459.           RTS            ;Return with bytes reversed
  460. *
  461. SINTBL    DS $F6         ;Leave $F6 bytes for SIN table
  462. *
  463. CMDTBL    ASC 'RDVMBCASLT'
  464. CALLTBL   DFB #<RAY-1,#<DOTLIN-1,#<VECTOR-1
  465.           DFB #<MOVEC-1,#<BARC-1
  466.           DFB #<CIRCLE-1,#<ARC-1,#<DODOT-1
  467.           DFB #<LTURN1-1,#<TURN-1
  468. END       EQU *
  469.           LST OFF
  470.